package com.zwz.shiro.chainDefinitionsFilter;

import java.util.List;
import java.util.Map;
import java.util.Set;
import org.apache.commons.lang.StringUtils;
import org.apache.shiro.config.Ini;
import org.apache.shiro.config.Ini.Section;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.util.CollectionUtils;
import org.apache.shiro.web.filter.mgt.DefaultFilterChainManager;
import org.apache.shiro.web.filter.mgt.PathMatchingFilterChainResolver;
import org.apache.shiro.web.servlet.AbstractShiroFilter;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import com.zwz.enums.UrlTypeEnum;
import com.zwz.service.baseConfig.SysResourceService;
import com.zwz.service.baseConfig.SysRoleService;

public class ChainDefinitionsFilterServiceImpl implements ChainDefinitionsFilterService {
	private static Logger logger = LoggerFactory.getLogger(ChainDefinitionsFilterServiceImpl.class);
	
	private String definitions;//默认静态资源
	public void setDefinitions(String definitions) {
		this.definitions = definitions;
	}
	
	@Autowired
	private ShiroFilterFactoryBean shiroFilterFactoryBean;
	@Autowired
	private SysResourceService sysResourceService;
	@Autowired
	private SysRoleService sysRoleService;

	public void initPermission() {
		logger.debug("==========初始化权限url start========");
		shiroFilterFactoryBean.setFilterChainDefinitionMap(loadPermission());
		logger.debug("==========初始化权限url end========");
	}

	public void updatePermission() {
        synchronized (shiroFilterFactoryBean) {  
            AbstractShiroFilter shiroFilter = null;  
            try {  
                shiroFilter = (AbstractShiroFilter) shiroFilterFactoryBean.getObject();  
            } catch (Exception e) {  
            	e.printStackTrace();
            }  
            // 获取过滤管理器  
            PathMatchingFilterChainResolver filterChainResolver = (PathMatchingFilterChainResolver) shiroFilter  
                    .getFilterChainResolver();  
            DefaultFilterChainManager manager = (DefaultFilterChainManager) filterChainResolver.getFilterChainManager();  
  
            // 清空初始权限配置  
            manager.getFilterChains().clear();  
            shiroFilterFactoryBean.getFilterChainDefinitionMap().clear();  
  
            // 重新构建生成  
            shiroFilterFactoryBean.setFilterChainDefinitionMap(loadPermission());
            Map<String, String> chains = shiroFilterFactoryBean.getFilterChainDefinitionMap();  
            if(!CollectionUtils.isEmpty(chains)){
	            for (Map.Entry<String, String> entry : chains.entrySet()) {  
	                String url = entry.getKey();  
	                String chainDefinition = entry.getValue().trim().replace(" ", "");  
	                manager.createChain(url, chainDefinition);  
	            }
            }
  
        } 
	}
	/**
	 * 加载资源链接
	 * @return
	 */
	private Section loadPermission(){
		Ini ini=new Ini();
		// 加载默认的url
		ini.load(definitions);
		Section section=ini.getSection(Ini.DEFAULT_SECTION_NAME);
		// 循环Resource的url,逐个添加到section中。section就是filterChainDefinitionMap,
		// 里面的键就是链接URL,值就是存在什么条件才能访问该链接
		//查询全部链接
		List<Map<String,String>> urls = sysResourceService.findAllUrl();
		for (Map<String, String> map : urls) {
			//roles
			if(UrlTypeEnum.URL_TYPE_0.getCode().equals(map.get("perimssion_type"))){
				Set<String> roleSet=sysRoleService.getRoleCodeByUrl(map.get("url"));
				String roleStr=StringUtils.join(roleSet, ",");
				section.put(map.get("url"), "roles["+roleStr+"]");
			}
			//perms
			else if(UrlTypeEnum.URL_TYPE_1.getCode().equals(map.get("perimssion_type"))){
				
			}
			//anon
			else if(UrlTypeEnum.URL_TYPE_2.getCode().equals(map.get("perimssion_type"))){
				section.put(map.get("url"), "anon");
			}
			//anonc
			else if(UrlTypeEnum.URL_TYPE_3.getCode().equals(map.get("perimssion_type"))){
				section.put(map.get("url"), "authc");
			}
		}
		// 所有资源的访问权限，必须放在最后
		section.put("/**", "authc");
		/*section.put("/test/get.do", "anon");
		section.put("/test/get1.do", "roles[user]");
		Long times=new Date().getTime();
		Long timess=10L;
		if(times<timess){
			section.put("/test/get2.do", "roles[admin]");
		}else{
			section.put("/test/get2.do", "roles[user]");
		}
		section.put("/test/get3.do", "roles[manage]");
		section.put("/test/get4.do", "perms[user,admin]");*/
		return section;
	}
	
}
